<template>
  <div class="organizational">
    <!--    <div class="backBtn">-->
    <!--      <el-button type="primary" size="small" icon="el-icon-arrow-left">返回</el-button>-->
    <!--    </div>-->
    <cusTree :treeData="dataM" @getId="getId"></cusTree>
    <!-- 添加部门的弹窗 -->
    <el-dialog title="添加部门" @open="addDepartmentBeFore" append-to-body width="500" :visible.sync="dialogFormVisible">
      <el-form :model="form" size="large">
        <el-form-item label="部门名称" label-width="80px">
          <el-input placeholder="请输入名称" v-model="form.name"></el-input>
        </el-form-item>
      </el-form>
      <div slot="footer" class="dialog-footer">
        <el-button @click="dialogFormVisible = false">取 消</el-button>
        <el-button type="primary" @click="addDepartment()">确 定</el-button>
      </div>
    </el-dialog>
    <!-- 添加工作组 -->
    <addTeam @updateData="getOrganizationById" :departmentId="addTeamDepartmentId" :organizationById="organizationById" v-model="addTeamVisible"></addTeam>
    <!-- 添加人员 -->
    <addPersonnel @updateData="getOrganizationById" v-model="showAddPersonnel" :departments="departments"></addPersonnel>
    <!-- 添加组织架构-->
    <el-dialog :append-to-body="true" :title="dialogTitle" @opened="resetFields" :visible.sync="showAddDislog">
      <el-form  :rules="rules" ref="ruleForm" label-width="130px" :model="addForm">
        <el-form-item label="组织id" prop="id">
          <el-input
              placeholder="请输入组织id"
              v-model="addForm.id"
              clearable>
          </el-input>
        </el-form-item>
        <el-form-item label="组织名称" prop="name">
          <el-input
              placeholder="请输入组织名称"
              v-model="addForm.name"
              clearable>
          </el-input>
        </el-form-item>
        <el-form-item label="简称" prop="shortName">
          <el-input
              placeholder="请输入简称"
              v-model="addForm.shortName"
              clearable>
          </el-input>
        </el-form-item>
        <el-form-item label="统一社会信用代码" prop="uniqueCode">
          <el-input
              placeholder="请输入统一社会信用代码"
              v-model="addForm.uniqueCode"
              clearable>
          </el-input>
        </el-form-item>
        <el-form-item label="上级组织机构" prop="parentId">
          <el-select v-model="addForm.parentId" disabled style="width: 100%;" placeholder="请选择上级组织机构">
            <el-option
                v-for="item in tableData"
                :key="item.id"
                :label="item.name"
                :value="item.id">
            </el-option>
          </el-select>
        </el-form-item>
        <el-form-item label="管理员姓名" prop="organAdminName">
          <el-input
              placeholder="请输入管理员姓名"
              v-model="addForm.organAdminName"
              clearable>
          </el-input>
        </el-form-item>
        <el-form-item label="管理员性别" prop="male">
          <el-radio-group v-model="addForm.male">
            <el-radio :label="true">男</el-radio>
            <el-radio :label="false">女</el-radio>
          </el-radio-group>
        </el-form-item>
      </el-form>
      <div slot="footer" class="dialog-footer">
        <el-button @click="cancel()">取 消</el-button>
        <el-button type="primary" @click="addFormRule()">确 定</el-button>
      </div>
    </el-dialog>
    <el-dialog :append-to-body="true" title="人员管理" :visible.sync="editTeamEmployees">
      <div>
        <el-input v-model="searchEmployeesForTeam"  placeholder="请输入名字搜索"></el-input>
      </div>
      <div class="employeesList" style="margin-bottom: 20px">
        <el-table
            :data="editTeamEmployeesList.filter(item => item.name.includes(searchEmployeesForTeam))"
            stripe
            style="width: 100%">
          <el-table-column
              prop="name"
              label="姓名">
          </el-table-column>
          <el-table-column
              fixed="right"
              label="操作"
              width="100">
            <template slot-scope="scope">
              <el-checkbox :true-label="1" :false-label="0" v-model="scope.row.checked"></el-checkbox>
            </template>
          </el-table-column>
        </el-table>
      </div>
      <div slot="footer" class="dialog-footer">
        <el-button @click="editTeamEmployees = false">取 消</el-button>
        <el-button type="primary" @click="updateTeamEmployees()">确 定</el-button>
      </div>
    </el-dialog>
  </div>
</template>

<script>
import cusTree from '@/components/tree/cus-tree.vue'
import addPersonnel from "@/components/addPersonnel/index.vue";
import addTeam from "@/components/addTeam/index.vue";

export default {
  name: 'organizational',
  data() {
    return {
      employeesList: [],
      tableData: [],
      permissions: {},
      searchEmployeesForTeam: '',
      editTeamEmployeesList: [],
      oldTeamEmployeesList: [],
      teamId: null,
      editTeamEmployees: false,
      showAddPersonnel: false,
      showAddDislog: false,
      dialogTitle: '添加组织机构',
      departments: [],
      dataM: {},
      allEmployees: [],
      dialogFormVisibleData: null,
      dialogFormVisible: false,
      mergeVisible: false,
      addTeamVisible: false,
      addTeamVisibleData: null,
      organizationById: null,
      addTeamDepartmentId: null,
      addForm: {
        id: '',
        name: '',
        shortName: '',
        uniqueCode: '',
        parentId: '',
        organAdminName: '',
        male:true
      },
      rules: {
        id: [
          { required: true, message: '请输入组织id', trigger: 'blur' },
        ],
        name: [
          { required: true, message: '请输入组织名称', trigger: 'blur' },
        ],
        organAdminName: [
          { required: true, message: '请输入管理员姓名', trigger: 'blur' },
        ],
        male: [
          { required: true, message: '请选择管理员性别', trigger: 'change' }
        ]
      },
      form: {
        name: '',
      },

      tsProps: {
        label: 'label',
        children: 'child'
      },
      mergeForm:{
        aType: 1,
        name: '',
        department: []
      }
    }
  },
  components: {
    addPersonnel,
    addTeam,
    cusTree
  },
  computed: {
    userInfo() {
      return this.$store.state.userInfo
    },
    employeeInfo() {
      return this.$store.state.employeeInfo
    },
  },
  methods: {
    // 重置添加组织架构的表单
    resetFields() {
      this.$refs.ruleForm.resetFields()
    },
    // 关闭组织架构的弹窗
    cancel() {
      this.$refs.ruleForm.resetFields()
      this.showAddDislog = false
    },
    // 添加组织架构的校验
    addFormRule() {
      this.$refs.ruleForm.validate((valid) => {
        if (valid) {
          this.addOne()
        } else {
          return false;
        }
      });
    },
    // 发起添加组织架构的请求
    async addOne() {
      const res = await this.$axios.post('/graphql', {
        query: `mutation {
            organizationManagementScene {
              createOrganization(
                id: "${this.addForm.id}"
                name: "${this.addForm.name}"
                shortName: "${this.addForm.shortName}"
                uniqueCode: "${this.addForm.uniqueCode}"
                parentId: "${this.addForm.parentId}"
                organAdminName: "${this.addForm.organAdminName}"
                male: ${this.addForm.male}
              )
            }
          }`
      })
      if (!res.data.errors) {
        this.addForm = {
          id: '',
          name: '',
          shortName: '',
          uniqueCode: '',
          parentId: '',
          organAdminName: '',
          male:true
        }
        this.showAddDislog = false
        this.getOrganizationById()
      }
    },
    // 获取组织架构用于下拉框
    async getData() {
      const res = await this.$axios.post('/graphql', {
        query: `{
          organizationQueryRepository {
            getItems {
              id
              removed
              uniqueCode
              name
              shortName
              employees {
                getItems {
                  id
                  name
                  pinyin
                  account {
                    displayName
                    actived
                  }
                }
              }
              parent {
                id
                name
                shortName
                uniqueCode
              }
              subordinates {
                getItems {
                  id
                  removed
                  uniqueCode
                  name
                  shortName
                }
              }
            }
          }
        }`
      })
      this.tableData = res.data.data.organizationQueryRepository.getItems
    },
    // 获取所属下级的组织架构的数据
    async getOrganizationForSubordinate(data) {
      const res = await this.$axios.post('/graphql', {
        query: `{
        organizationQueryRepository {
          findById(id: "${data.id}") {
            id
            removed
            uniqueCode
            name
            shortName
            subordinates {
              getItems {
                id
                name
              }
            }
            employees {
              getItems {
                id
                name
                pinyin
                phoneNumber
                officialRank
                isMale
                removed
                department {
                  id
                  name
                }
              }
            }
            departments {
              getItems {
                id
                removed
                name
                employees {
                 id
                 name
                 pinyin
                 removed
                    phoneNumber
                    officialRank
                    isMale
                    department {
                      id
                      name
                    }
                }
                 getTeams {
                   id
                   name
                   getItems {
                     id
                     name
                   }
                 }
              }
            }
            teams {
              getItems {
                 id
                 name
                 department {
                    id
                    name
                 }
                 getItems {
                    id
                    name
                 }
              }
            }
          }
        }
      }`}
      )

      if (!res.data.errors) {
        const mOperate = []
        const operate = []
        if ( this.permissions.createTeam) {
          operate.push({
            funName: 'addWorkgroups',
            btnName: '添加工作组'
          })
        }
        if ( this.permissions.mergeDepartment) {
          operate.push({
            funName: 'mergeDepartment',
            btnName: '合并部门'
          })
        }
        if ( this.permissions.revokeDepartment) {
          operate.push({
            funName: 'revokeDepartment',
            btnName: '撤销部门'
          })
        }
        if ( this.permissions.admin) {
          mOperate.push({
            funName: 'mergeWorkgroups',
            btnName: '合并工作组'
          })
        }
        if ( this.permissions.destoryTeam) {
          mOperate.push({
            funName: 'revokeWorkgroup',
            btnName: '撤销工作组'
          })
        }
        if ( this.permissions.queryEmployee) {
          operate.push({
            funName: 'departmentEmployees',
            btnName: '人员管理'
          })
        }
        if ( this.permissions.teamAddMember) {
          mOperate.push({
            funName: 'editTeamEmployees',
            btnName: '人员管理'
          })
        }

        const nData = res.data.data.organizationQueryRepository.findById
        const subordinates = nData.subordinates.getItems
        const subordinatesLength = nData.subordinates.getItems.length
        if (subordinatesLength !== 0) {
          for(let a = 0 ; a< subordinatesLength; a++) {
            if (!subordinates[a].removed) {
              this.getOrganizationForSubordinate(subordinates[a])
            }
          }
        }else {
          const dataM = {
            ...nData,
            label: nData.name,
            child: []
          }
          const departments = nData.departments.getItems
          const employees = nData.employees.getItems
          const teams = nData.teams.getItems
          departments.forEach(item => {
            const team = []
            item.getTeams.forEach(aItem => {
              team.push({
                label: aItem.name,
                type: 'teams',
                ...aItem,
                child: [],
                operate: mOperate
              })
            })

            dataM.child.push({
              label: item.name,
              id: item.id,
              type: 'department',
              child: [],
              operate: operate
            })
          })

          teams.forEach(item => {
            if (!item.department) {
              dataM.child.push({
                label: item.name,
                type: 'teams',
                ...item,
                child: [],
                operate: mOperate
              })
            }
          })
          return dataM
        }
      }
    },
    // 获取当前用户拥有的权限
    getAuthorizationQueryRepository() {
      const organId = this.employeeInfo.organization.id
      this.permissions = {
        admin: `organization:admin:${organId}`,
        createTeam: [
          `organization/team:createTeam:${organId}`,
          `organization:admin:${organId}`
        ],
        destoryTeam: [
          `organization/team:destory:${organId}`,
          `organization:admin:${organId}`
        ],
        queryEmployee: [
          `organization/employee:query:${organId} `,
          `organization:admin:${organId}`
        ],
        revokeDepartment: [
          `organization/department:revoke:${organId}`,
          `organization:admin:${organId}`
        ],
        establishDepartment: [
          `organization/department:establish:${organId}`,
          `organization:admin:${organId}`
        ],
        teamAddMember: [
          `organization/team:addMember:${organId}`,
          `organization/team:removeMember:${organId}`,
          `organization:admin:${organId}`
        ],
        mergeDepartment: [
          `organization/department:merge:${organId}`,
          `organization:admin:${organId}`
        ],
      }
      this.permissions = this.$common.checkPermissions(this.permissions)
    },
    // 输出组织架构图的数据接口
    async getDataType(data) {
      const departments = data.departments.getItems
      this.departments = departments
      const mOperate = []
      const operate = []
      if ( this.permissions.createTeam) {
        operate.push({
          funName: 'addWorkgroups',
          btnName: '添加工作组'
        })
      }
      if ( this.permissions.mergeDepartment) {
        operate.push({
          funName: 'mergeDepartment',
          btnName: '合并部门'
        })
      }
      if ( this.permissions.revokeDepartment) {
        operate.push({
          funName: 'revokeDepartment',
          btnName: '撤销部门'
        })
      }
      if ( this.permissions.admin) {
        mOperate.push({
          funName: 'mergeWorkgroups',
          btnName: '合并工作组'
        })
      }
      if ( this.permissions.destoryTeam) {
        mOperate.push({
          funName: 'revokeWorkgroup',
          btnName: '撤销工作组'
        })
      }
      if ( this.permissions.queryEmployee) {
        operate.push({
          funName: 'departmentEmployees',
          btnName: '人员管理'
        })
      }
      if ( this.permissions.teamAddMember) {
        mOperate.push({
          funName: 'editTeamEmployees',
          btnName: '人员管理'
        })
      }
      this.allEmployees = data.employees.getItems
      const teams = data.teams.getItems
      departments.forEach(item => {
        const employees = []
        const team = []
        item.employees && item.employees.forEach(aItem => {
          employees.push({
            label: aItem.name,
            type: 'employees',
            ...aItem,
            child: [],
            operate: [
              {
                funName: 'employeesDetails',
                btnName: '员工详情'
              },
              {
                funName: 'leaveOffice',
                btnName: '离职'
              },
            ]
          })
        })
        item.getTeams && item.getTeams.forEach(aItem => {
          team.push({
            label: aItem.name,
            type: 'teams',
            ...aItem,
            child: [],
            operate: mOperate
          })
        })
        this.dataM.child.push({
          label: item.name,
          id: item.id,
          type: 'department',
          child: team,
          operate: operate
        })
      })
      teams.forEach(item => {
        if (!item.department) {
          this.dataM.child.push({
            label: item.name,
            type: 'teams',
            ...item,
            child: [],
            operate: mOperate
          })
        }
      })
    },
    async updateTeamEmployees() {
      let data = []
      let addMembersText = ''
      let removeMembersText = ''
      this.editTeamEmployeesList.map(item => {
        if (item.checked === 1) {
          data.push(item.id)
        }
      })
      const addArr = []

      data.map(item => {
        if (!this.oldTeamEmployeesList.includes(item)) {
          addArr.push(item)
        }
      })
      const delArr = []
      this.oldTeamEmployeesList.map(item => {
        if (!data.includes(item)) {
          delArr.push(item)
        }
      })

      if (addArr.length !== 0) {
        addMembersText = `addMembers(id: "${this.teamId}", memberIds: ["${addArr.toString()}"])`
      }
      if (delArr.length !== 0) {
        removeMembersText = `removeMembers(id: "${this.teamId}", memberIds: ["${delArr.toString()}"])`
      }
      if (addArr.length === 0 && delArr.length === 0 ) {
        return false
      }
      const res = await this.$axios.post('/graphql', {
        query: `mutation {
          teamManagementScene {
             ${ addArr.length !== 0 ? addMembersText : ''}
             ${ delArr.length !== 0 ? removeMembersText : '' }
          }
        }`
      })
      if (!res.data.errors) {
        this.editTeamEmployees = false
        this.$message.success('修改成功')
        this.getOrganizationById()
      }else {
        this.$message.error(res.data.errors[0].message)
      }
    },
    // 组织架构图的点击事件
    getId(obj) {
      let arr = []

      switch (obj.fun)
      {
        case 'organizationEmployees':
          this.$router.push(`/userList`)
          break;
        case 'departmentEmployees':
          this.$router.push(`/userList`)
          break;
        case 'editTeamEmployees':
          obj.data.getItems.map(item => {
            arr.push(item.id)
          })
          this.teamId = obj.data.id
          this.oldTeamEmployeesList = arr
          this.editTeamEmployeesList = []
          this.employeesList.forEach(item => {
            this.editTeamEmployeesList.push({
              ...item,
              checked: arr.includes(item.id) ? 1 : 0
            })
          })
          this.editTeamEmployees = true
          break
        case 'addEmployees':
          this.showAddPersonnel = true
          break;
        case 'employeesDetails':
          this.$router.push(`/editPersonnel?id=${obj.data.id}`)
          break;
        case 'addDepartment':
          this.dialogFormVisible = true
          this.dialogFormVisibleData = obj.data
          break;
        case 'leaveOffice':
          this.leaveOfficeFun(obj.data)
          break;
        case 'addWorkgroups':
          this.addTeamDepartmentId = obj.data.id
          this.addTeamVisible = true
          this.addTeamVisibleData = obj.data
          break;
        case 'addOrganization':
          this.addForm.parentId = obj.data.id
          this.showAddDislog = true
          break
        case 'seeOrganization':
          break
        case 'revokeDepartment':
          this.revokeDepartmentFun(obj.data)
      }
    },
    // 重置部门名称输入框
    async addDepartmentBeFore() {
      this.form.name = ''
    },
    // 裁撤部门的提示
    revokeDepartmentFun(data) {
      this.$confirm('是否裁撤该部门?', '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(() => {
        this.goRevokeDepartment(data)
      }).catch(() => {
        this.$message({
          type: 'info',
          message: '已取消'
        });
      });
    },
    // 裁撤部门
    async goRevokeDepartment(data) {
      const res = await this.$axios.post('/graphql', {
        query: `mutation {
          organizationScene {
            revokeDepartment(deptId: "${data.id}")
          }
        }`
      })
      if (!res.data.errors) {
        this.$message({
          type: 'success',
          message: '已办理!'
        });
        await this.getOrganizationById()
      }
    },
    // 添加部门
    async addDepartment () {
      const res = await this.$axios.post('/graphql', {
        query: `mutation {
          organizationScene {
            establishDepartment(
               name: "${this.form.name}"
               parentId: "${this.dialogFormVisibleData.id}"
            )
          }
        }`
      })
      if (!res.data.errors) {
        this.dialogFormVisible = false
        this.$message.success('添加成功')
        await this.getOrganizationById()
      }
    },
    // 添加工作组
    async addTeam() {
      const res = await this.$axios.post('/graphql', {
        query: `mutation {
          teamManagementScene {
            createTeam(
              departmentId: "string"
              name: "string"
              description: "string"
              chargeId: "string"
              tags: ["string"]
              memberIds: ["string"]
            )
          }
        }`
      })
      if (!res.data.errors) {
        this.dialogFormVisible = false
        this.$message.success('添加成功')
        await this.getOrganizationById()
      }
    },
    // 离职
    async goLeaveOffice(data) {
      const res = await this.$axios.post('/graphql', {
        query: `mutation {
          employeeManagementScene {
            leaveOffice(id: "${data.id}")
          }
        }`
      })
      if (!res.data.errors) {
        this.$message({
          type: 'success',
          message: '已办理!'
        });
        await this.getOrganizationById()
      }
    },
    // 离职操作提示
    leaveOfficeFun(data) {
      this.$confirm('是否办理离职?', '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(() => {
        this.goLeaveOffice(data)
      }).catch(() => {
        this.$message({
          type: 'info',
          message: '已取消'
        });
      });
    },
    // 获取当前的组织架构信息
    async getOrganizationById() {
      const res = await this.$axios.post('/graphql', {
        query: `{
          organizationQueryRepository {
            findById(id: "${this.organizationById}"){
              id
              removed
              uniqueCode
              name
              shortName
              parent {
                id
                name
              }
            }
          }
        }`
      })
      if (!res.data.errors) {
        const operate = []
        if ( this.permissions.establishDepartment) {
          operate.push({
            funName: 'addDepartment',
            btnName: '添加部门'
          })
        }
        if ( this.permissions.createTeam) {
          operate.push({
            funName: 'addWorkgroups',
            btnName: '添加工作组'
          })
        }
        if ( this.permissions.queryEmployee) {
          operate.push({
            funName: 'departmentEmployees',
            btnName: '人员管理'
          })
        }

        this.dataM = {
          ...res.data.data.organizationQueryRepository.findById,
          label: res.data.data.organizationQueryRepository.findById.name,
          child: [],
          operate: operate
        }
        await this.getTableData(this.organizationById)
      }
    },
    // 通过组织架构获取组织架构的人员信息、工作组、部门、所属组织架构
    async getTableData(id) {
      const res = await this.$axios.post('/graphql', {
        query: `{
        organizationQueryRepository {
          findById(id: "${id}") {
            id
            removed
            uniqueCode
            name
            shortName
            subordinates {
              getItems {
                id
                name
              }
            }
            employees {
              getItems {
                id
                name
                pinyin
                phoneNumber
                officialRank
                isMale
                removed
                department {
                  id
                  name
                }
              }
            }
            departments {
              getItems {
                id
                removed
                name
                employees {
                 id
                 name
                 pinyin
                 removed
                    phoneNumber
                    officialRank
                    isMale
                    department {
                      id
                      name
                    }
                }
                 getTeams {
                   id
                   name
                   getItems {
                     id
                     name
                   }
                 }
              }
            }
            teams {
              getItems {
                 id
                 name
                 department {
                    id
                    name
                 }
                 getItems {
                    id
                    name
                 }
              }
            }
          }
        }
      }`})
      this.getDataType(res.data.data.organizationQueryRepository.findById)
    },
    async getTemployeesList() {
      const res = await this.$axios.post('/graphql', {
        query: `{
        organizationQueryRepository {
          findById(id: "${this.employeeInfo.organization.id}") {
            id
            removed
            uniqueCode
            name
            shortName
            employees {
              getItems {
                id
                name
                pinyin
                phoneNumber
                officialRank
                isMale
                removed
                department {
                  id
                  name
                }
              }
            }
            departments {
              getItems {
                id
                removed
                name
                employees {
                 id
                 name
                 pinyin
                 removed
                    phoneNumber
                    officialRank
                    isMale
                    department {
                      id
                      name
                    }
                }
                getTeams {
                    id
                    name
                    getItems {
                     id
                     name
                   }
                }
              }
            }
            teams {
              getItems {
                id
                name
                getItems {
                  id
                  name
                }
              }
            }
          }

}
}
`})
      // = res.data.data.organizationQueryRepository.findById.departments.getItems
      this.employeesList = res.data.data.organizationQueryRepository.findById.employees.getItems
    },
    // 打开添加工作组前清空数组
    addTeamBeFore() {
      this.addTeamForm = {
        departmentId: '',
        name: '',
        description: '',
        chargeId: '',
        tags: '',
        memberIds: []
      }
    },
  },
  watch: {},
  async created() {
    await this.getAuthorizationQueryRepository()
    this.getData()
    this.getTemployeesList()
    if (this.$route.query.id) {
      this.organizationById = this.$route.query.id
      this.getOrganizationById()
    }else {
      this.$nextTick(() => {
        this.organizationById = this.employeeInfo.organization.id
        this.getOrganizationById()
      })
    }
  },
  async activated() {
    await this.getAuthorizationQueryRepository()
    this.getData()
    this.getTemployeesList()
    if (this.$route.query.id) {
      this.organizationById = this.$route.query.id
      this.getOrganizationById()
    }else {
      this.$nextTick(() => {
        this.organizationById = this.employeeInfo.organization.id
        this.getOrganizationById()
      })
    }
  },
}
</script>

<style scoped lang="scss">
.organizational {
  width: 100%;
  height: 100%;
  position: relative;
  background-color: #ffffff;
  box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
}

.backBtn {
  position: absolute;
  width: max-content;
  top: 10px;
  left: 10px;
  z-index: 1000;
}

.dialog-footer {
  width: 100%;
  height: auto;
  text-align: right;
}

</style>
